package com.cloud.mybatis.config;

import cn.hutool.core.text.AntPathMatcher;
import cn.hutool.core.util.CharsetUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.crypto.symmetric.SymmetricCrypto;
import cn.hutool.extra.spring.SpringUtil;
import cn.hutool.json.JSONUtil;
import com.cloud.core.constant.ErrorCodeConstant;
import com.cloud.core.constant.SecurityConstants;
import com.cloud.core.entity.base.LoginUser;
import com.cloud.core.util.R;
import com.cloud.mybatis.utils.WebHttpApi2;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.springframework.context.i18n.LocaleContextHolder;
import org.springframework.context.i18n.SimpleLocaleContext;
import org.springframework.web.servlet.AsyncHandlerInterceptor;

import java.util.*;

@Slf4j
public class AccessFilter implements AsyncHandlerInterceptor {
    AntPathMatcher matcher = new AntPathMatcher();
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        if(matcher.match( "/*/v3/api-docs/*", request.getRequestURI())){
            return true;
        }
        if(matcher.match( "/*/doc.html", request.getRequestURI())){
            return true;
        }
        if(matcher.match( "/*/v3/api-docs", request.getRequestURI())){
            return true;
        }
        if(matcher.match( "/*/swagger-ui/*",request.getRequestURI())){
            return true;
        }
        String secFlag = request.getHeader("SEC_FLAG");
        if (StrUtil.isBlank(secFlag)) {
            forbid(response);
            return false;
        }
        SymmetricCrypto sm = SpringUtil.getBean(cn.hutool.crypto.symmetric.SymmetricCrypto.class);

        String decryptStr = sm.decryptStr(secFlag, CharsetUtil.CHARSET_UTF_8);

        long utc = Long.parseLong(decryptStr);
        long subSec = (System.currentTimeMillis() - utc) / 1000;
        log.info("utc:{},subSec:{}", utc, subSec);
        if (subSec > 2) {
            forbid(response);
            return false;
        }



        String acceptLanguage = request.getHeader(SecurityConstants.ACCEPT_LANGUAGE);
        Locale locale = Locale.getDefault();
        HashMap<String, Object> context = new HashMap<>();
        if (acceptLanguage != null && acceptLanguage.length() > 1) {
            String[] split = acceptLanguage.split("_");
            if (split.length > 1) {
                locale = new Locale(split[0], split[1]);
                LocaleContextHolder.setLocaleContext(new SimpleLocaleContext(locale), true);
                context.put(SecurityConstants.ACCEPT_LANGUAGE, locale);
            }
        }
        String userStr = request.getHeader(SecurityConstants.USER);

        if (StrUtil.isNotEmpty(userStr)) {
            LoginUser user = JSONUtil.toBean(userStr, LoginUser.class);
            context.put(SecurityConstants.USER, user);
            LoginHolder.setContext(context);
            getPermitData();
            if(LoginHolder.mapperFunSet.size()==0) {
                getGlobalFun();
            }
        }




        return true;
    }
    @SneakyThrows
    private void forbid(HttpServletResponse response) {
        response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
        response.setContentType("application/json;charset=utf-8");
        response.getWriter().write(JSONUtil.toJsonPrettyStr(R.failed(null, "no auth")));
    }
    public void getPermitData() {
        long currentUTC = System.currentTimeMillis();
        SymmetricCrypto sm = SpringUtil.getBean(cn.hutool.crypto.symmetric.SymmetricCrypto.class);
        String encryptHex = sm.encryptHex(currentUTC+"");
        R<LinkedHashMap> result = WebHttpApi2.get("http://sys-permit/sys-permit/user-dept/getUserDeptRoleScope", null,null,R.class);
        if(result.getCode().intValue() == ErrorCodeConstant.SUCCESS) {
          LinkedHashMap<String,Object> data  = result.getData();
          LoginHolder.setRoleScope(data);
        }
    }
    public void getGlobalFun() {
        MapperFuns funcs = SpringUtil.getBean(MapperFuns.class);
        for (String fun : funcs.getFunctions()){
            LoginHolder.setMapperFuns(fun);
        }
        /*R   result = WebHttpApi2.get("http://sys-permit/sys-permit/user-dept/getAllFuns" , null,null, R.class);
        if(result.getCode().intValue() == ErrorCodeConstant.SUCCESS) {
             ArrayList data = (ArrayList) result.getRows();
             for(Object m : data) {
                 LinkedHashMap map = (LinkedHashMap) m;
                 LoginHolder.setMapperFuns(map.get("funId").toString() );
             }

        }*/
    }
}
